/**
 * Copyright (C) 2010-2016 eBusiness Information, Excilys Group
 * Copyright (C) 2016-2020 the AndroidAnnotations project
 * <p>
 * Licensed under the Apache License, Version 2.0 (the "License"); you may not
 * use this file except in compliance with the License. You may obtain a copy of
 * the License at
 * <p>
 * http://www.apache.org/licenses/LICENSE-2.0
 * <p>
 * Unless required by applicable law or agreed To in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
 * License for the specific language governing permissions and limitations under
 * the License.
 */

package org.ohosannotations.internal;

import org.ohosannotations.Option;
import org.ohosannotations.helper.ModelConstants;
import org.ohosannotations.holder.BaseGeneratedClassHolder;
import org.ohosannotations.internal.generation.CodeModelGenerator;
import org.ohosannotations.internal.helper.OhosManifestFinder;
import org.ohosannotations.internal.rclass.ProjectRClassFinder;
import org.ohosannotations.logger.LoggerContext;
import org.ohosannotations.logger.appender.FileAppender;

import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.TreeSet;

import javax.annotation.processing.ProcessingEnvironment;

/**
 * 选项
 *
 * @author dev
 * @since 2021-07-22
 */
public class Options {
    private final Map<String, Option> supportedOptions = new HashMap<>();
    private final Map<String, String> options;

    /**
     * 选项
     *
     * @param processingEnvironment 处理环境中
     */
    public Options(ProcessingEnvironment processingEnvironment) {
        options = processingEnvironment.getOptions();
        addSupportedOption(OhosManifestFinder.OPTION_MANIFEST);
        addSupportedOption(OhosManifestFinder.OPTION_LIBRARY);
        addSupportedOption(OhosManifestFinder.OPTION_INSTANT_FEATURE);
        addSupportedOption(ProjectRClassFinder.OPTION_RESOURCE_PACKAGE_NAME);
        addSupportedOption(ProjectRClassFinder.OPTION_USE_R2);
        addSupportedOption(ModelConstants.OPTION_CLASS_SUFFIX);
        addSupportedOption(FileAppender.OPTION_LOG_FILE);
        addSupportedOption(LoggerContext.OPTION_LOG_LEVEL);
        addSupportedOption(LoggerContext.OPTION_LOG_APPENDER_CONSOLE);
        addSupportedOption(LoggerContext.OPTION_LOG_APPENDER_FILE);
        addSupportedOption(BaseGeneratedClassHolder.OPTION_GENERATE_FINAL_CLASSES);
        addSupportedOption(CodeModelGenerator.OPTION_ENCODING);
        addSupportedOption(OhosAnnotationProcessor.OPTION_INCREMENTAL);
    }

    /**
     * 添加所有支持的选项
     *
     * @param options 选项
     */
    public void addAllSupportedOptions(List<Option> options) {
        for (Option option : options) {
            addSupportedOption(option);
        }
    }

    /**
     * 添加支持选项
     *
     * @param option 选项
     */
    private void addSupportedOption(Option option) {
        supportedOptions.put(option.getName(), option);
    }

    /**
     * 得到
     *
     * @param option 选项
     * @return {@link String}
     */
    public String get(Option option) {
        String value = options.get(option.getName());
        return value != null ? value : option.getDefaultValue();
    }

    /**
     * get
     *
     * @param optionKey optionKey
     * @return get
     */
    public String get(String optionKey) {
        Option option = supportedOptions.get(optionKey);
        if (option != null) {
            return get(option);
        } else {
            return options.get(optionKey);
        }
    }

    /**
     * getBoolean
     *
     * @param option option
     * @return Boolean
     */
    public boolean getBoolean(Option option) {
        return Boolean.valueOf(get(option));
    }

    /**
     * getBoolean
     *
     * @param optionKey optionKey
     * @return Boolean
     */
    public boolean getBoolean(String optionKey) {
        return Boolean.valueOf(get(optionKey));
    }

    /**
     * getSupportedOptions
     *
     * @return withIncremental
     */
    public Set<String> getSupportedOptions() {
        if (getBoolean(OhosAnnotationProcessor.OPTION_INCREMENTAL)) {
            Set<String> withIncremental = new TreeSet<>(supportedOptions.keySet());
            withIncremental.add("org.gradle.annotation.processing.isolating");
            return withIncremental;
        }
        return supportedOptions.keySet();
    }
}
